﻿using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using Daq.Devices;
using Daq.Services;
using Microsoft.Extensions.DependencyInjection;
using Serilog;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Input;
using System.Windows.Navigation;

namespace Daq.ViewModels.DeviceSettingsViewModels
{
    public partial class ConnectionViewModel : ObservableObject
    {
        private readonly INavigationService _navigationService;
        private readonly DeviceService _deviceService;
        private readonly SettingsService _settings;
        private readonly ILogger logger;
        private readonly IDialogService dialogService;
        public ConnectionViewModel(INavigationService navigationService, IDialogService dialogService, DeviceService deviceService, SettingsService settings, ILogger logger)
        {
            _navigationService = navigationService;
            _deviceService = deviceService;
            _settings = settings;
            this.dialogService = dialogService;
            this.logger = logger;
        }

        [RelayCommand]
        private void Test()
        {
            _navigationService.NavigateTo<MeasurementViewModel>();
        }

        [ObservableProperty]
        private ObservableCollection<DeviceInfo>? availableDaqs;

        [ObservableProperty]
        [NotifyCanExecuteChangedFor(nameof(GoToNextStepCommand))]
        private ObservableCollection<DeviceInfo?>? selectedDaqs;

        [ObservableProperty]
        [NotifyCanExecuteChangedFor(nameof(DeleteSelectedDaqsCommand))]
        private DeviceInfo? daqToBeDeleted;

        [ObservableProperty]
        [NotifyCanExecuteChangedFor(nameof(AddDeviceCommand))]
        [NotifyCanExecuteChangedFor(nameof(ModifySettingsCommand))]
        private DeviceInfo? daqToBeAdded;

        [ObservableProperty]
        private bool isBusy;
        [ObservableProperty]
        private string? busyContent;
        private bool CanDaqBeDeleted() => DaqToBeDeleted != null;
        private bool CanDaqBeAdded() => DaqToBeAdded != null;
        private bool CanModify() => DaqToBeAdded != null;

        [RelayCommand]
        public async Task SearchDevices()
        {
            BusyContent = "搜索设备";
            IsBusy = true;
            logger.Information("搜索设备");
            try
            {
                AvailableDaqs = new ObservableCollection<DeviceInfo>(await _deviceService.Search());
                logger.Information($"搜索到{AvailableDaqs.Count}个设备");
            }
            catch (Exception ex)
            {
                logger.Error($"搜索设备错误:{ex.Message}");
            }
            IsBusy = false;
        }

        [RelayCommand(CanExecute = nameof(CanModify))]
        private async Task ModifySettings()
        {
            if (DaqToBeAdded == null || DaqToBeAdded.Model == null || DaqToBeAdded.SN == null) return;
            var result = await dialogService.ShowEditIpDialogAsync(DaqToBeAdded.Model, DaqToBeAdded.SN, DaqToBeAdded.Address, DaqToBeAdded.NetMask);
            if(result)
            {
                SelectedDaqs = null;
                await SearchDevices();
            }
        }

        [RelayCommand(CanExecute = nameof(CanDaqBeAdded))]
        private void AddDevice(object obj)
        {
            if (obj is DeviceInfo device)
            {
                SelectedDaqs ??= [];
                //SelectedDaqs.Clear();
                _settings.Devices ??= [];
                _settings.Devices.Clear();
                if (!SelectedDaqs.Any(daq => daq != null && (daq.Address == device.Address || daq.SN == device.SN)))
                {
                    SelectedDaqs.Add(device);
                    //_settings.Devices.Add(device);
                }
                _settings.Devices = [.. SelectedDaqs];
            }
            GoToNextStepCommand.NotifyCanExecuteChanged();
        }

        [RelayCommand(CanExecute = nameof(CanDaqBeDeleted))]
        private void DeleteSelectedDaqs(Object obj)
        {
            if (SelectedDaqs == null)
            {
                return;
            }
            if (obj is DeviceInfo device)
            {
                SelectedDaqs.Remove(device);
            }
            _settings.Devices = [.. SelectedDaqs];
            GoToNextStepCommand.NotifyCanExecuteChanged();
        }
        [RelayCommand(CanExecute = nameof(CanGoToNextStep))]
        private void GoToNextStep()
        {
            logger.Information($"已添加设备：{string.Join(',', SelectedDaqs.Select(daq=>daq.Model).ToArray())},跳转到通道设置页面");
            var vm = App.Current.Services.GetService<DeviceSettingsViewModel>();
            vm?.SelectStep("通道设置");
        }

        private bool CanGoToNextStep => SelectedDaqs != null && SelectedDaqs.Count > 0;
    }
}
